package com.party.admin.task;

import com.party.core.model.member.Member;
import com.party.core.model.member.MemberGroup;
import com.party.core.service.circle.ICircleApplyService;
import com.party.core.service.competition.ICompetitionMemberService;
import com.party.core.service.crowdfund.IProjectService;
import com.party.core.service.crowdfund.ISupportService;
import com.party.core.service.distributor.IDistributorRelationService;
import com.party.core.service.gatherForm.IGatherFormInfoService;
import com.party.core.service.gatherInfo.IGatherInfoMemberService;
import com.party.core.service.member.IMemberActService;
import com.party.core.service.member.IMemberGroupService;
import com.party.core.service.member.IPartnerMemberService;
import com.party.core.service.sign.ISignApplyService;
import org.apache.commons.collections.CollectionUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.*;

/**
 * @Description: 会员管理的列表数据初始化
 * @Author: yangshoukun
 * @Date: 2018/2/27 18:18
 */
@Component("quartzMemberMgmt")
public class QuartzMemberMgmt {

    private static Logger log = LoggerFactory.getLogger(QuartzMemberMgmt.class);

    @Autowired
    private IMemberActService memberActService;
    @Autowired
    private IProjectService projectService;
    @Autowired
    private ISupportService supportService;
    @Autowired
    private IDistributorRelationService distributorRelationService;
    @Autowired
    private ICircleApplyService circleApplyService;
    @Autowired
    private ISignApplyService signApplyService;
    @Autowired
    private ICompetitionMemberService competitionMemberService;
    @Autowired
    private IGatherInfoMemberService gatherInfoMemberService;
    @Autowired
    private IGatherFormInfoService gatherFormInfoService;

    @Autowired
    private IMemberGroupService memberGroupService;
    @Autowired
    private IPartnerMemberService partnerMemberService;

    /**
     * 开始初始化/矫正
     */
    public void init() {
        try {
            log.info("开始进行----会员管理的列表数据初始化/矫正");
            List<MemberGroup> partners = memberGroupService.getAllPartnerNoOpenStatus();
            for (MemberGroup partner: partners) {
                insertPartnerMember(partner.getId());
            }
//            insertPartnerMember("949b34062d7e4ce685421df3889e6319");
            log.info("会员管理的列表数据初始化/矫正----结束");
        } catch (Exception e) {
            log.error("会员管理的列表数据初始化/矫正失败", e);
        }
    }

    /**
     * 某个机构的数据写入
     * @param partnerId
     */
    private void insertPartnerMember(String partnerId) {
        // 所有统计成员
        List<Member> members = getAllMembers(partnerId);
        // 所有已经有关系的成员
        List<Member> exists = getPartnerMembers(partnerId);

        Iterator<Member> it = members.iterator();
        Member temp;
        while (it.hasNext()) {
            temp = it.next();
            for (Member member: exists) {
                if (temp.getId().equals(member.getId())) {
                    it.remove();
                    exists.remove(member);
                    break;
                }
            }
        }

        // 去掉已经有的数据后, 如果还有新的数据, 就写入
        if (members.size() < 1) {
            return;
        }
        for (Member member: members) {
            partnerMemberService.insert(partnerId, member.getId(), member.getCreateDate());
        }
    }

    /**
     * 通过机构id查询partner_member表中已经有的会员, 有就不用插入了
     * @param partnerId
     * @return
     */
    private List<Member> getPartnerMembers(String partnerId) {
        return partnerMemberService.getMembersByPartnerId(partnerId);
    }

    /**
     * 计算所有要统计的成员
     * @return
     */
    private List<Member> getAllMembers(String partnerId) {
        List<Member> list = new ArrayList<>();
        addListToSet(list, getActMembersByPartnerId(partnerId));
        addListToSet(list, getZcMembersByPartnerId(partnerId));
        addListToSet(list, getZcSupportersByPartnerId(partnerId));
        addListToSet(list, getDistributorsByPartnerId(partnerId));
        addListToSet(list, getCircleApplicantsByPartnerId(partnerId));
        addListToSet(list, getSignApplicantsByPartnerId(partnerId));
        addListToSet(list, getCompetitionMembersByPartnerId(partnerId));
        addListToSet(list, getGatherInfoMembersByPartnerId(partnerId));
        addListToSet(list, getGatherFormInfoMembersByPartnerId(partnerId));

        Map<String, Date> map = new HashMap<>();

        list.forEach(member -> {
            String id = member.getId();
            if (map.get(id) == null) {
                map.put(id, member.getCreateDate());
            } else {
                if (map.get(id).getTime() > member.getCreateDate().getTime()) {
                    // 如果map中存的时间大于member中的时间, 则将member中的时间赋值给map中
                    map.get(id).setTime(member.getCreateDate().getTime());
                }
            }
        });

        List<Member> newList = new ArrayList<>();
        Member m;
        for (Map.Entry<String, Date> entry: map.entrySet()) {
            m = new Member();
            m.setId(entry.getKey());
            m.setCreateDate(entry.getValue());
            newList.add(m);
        }

        /*list = list.stream().collect(Collectors.collectingAndThen(Collectors.toCollection(
                () -> new TreeSet<>(Comparator.comparing(Member::getId))
        ), ArrayList::new));*/
        return newList;
    }

    private void addListToSet(List<Member> all, List<Member> list) {
        if (CollectionUtils.isEmpty(list)) {
            return;
        }
        all.addAll(list);
    }

    /**
     * 查询某机构下的所有活动报名者
     * @param partnerId
     * @return
     */
    private List<Member> getActMembersByPartnerId(String partnerId) {
        return memberActService.getActMembersByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有众筹名者
     * @param partnerId
     * @return
     */
    private List<Member> getZcMembersByPartnerId(String partnerId) {
        return projectService.getZcMembersByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有众筹支持者
     * @param partnerId
     * @return
     */
    private List<Member> getZcSupportersByPartnerId(String partnerId) {
        return supportService.getZcSupportersByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有分销者(包括活动分销和众筹联合发起)
     * @param partnerId
     * @return
     */
    private List<Member> getDistributorsByPartnerId(String partnerId) {
        return distributorRelationService.getDistributorsByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有圈子报名者
     * @param partnerId
     * @return
     */
    private List<Member> getCircleApplicantsByPartnerId(String partnerId) {
        return circleApplyService.getCircleApplicantsByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有运动签到(打卡)的人
     * @param partnerId
     * @return
     */
    private List<Member> getSignApplicantsByPartnerId(String partnerId) {
        return signApplyService.getSignApplicantsByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有赛事项目的参加者
     * @param partnerId
     * @return
     */
    private List<Member> getCompetitionMembersByPartnerId(String partnerId) {
        return competitionMemberService.getCompetitionMembersByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有人员信息收集(包括基础信息和行程)
     * @param partnerId
     * @return
     */
    private List<Member> getGatherInfoMembersByPartnerId(String partnerId) {
        return gatherInfoMemberService.getGatherInfoMembersByPartnerId(partnerId);
    }

    /**
     * 查询某机构下的所有登录过的自定义人员收集的人
     * @param partnerId
     * @return
     */
    private List<Member> getGatherFormInfoMembersByPartnerId(String partnerId) {
        return gatherFormInfoService.getGatherFormInfoMembersByPartnerId(partnerId);
    }

}
